package com.ody.util.code.config;

import com.odianyun.util.exception.ExceptionUtils;
import com.odianyun.util.io.FileUtils;
import com.ody.util.code.PlaceHolderHelper;

import javax.swing.*;
import java.awt.*;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.io.File;
import java.util.*;
import java.util.Map.Entry;

public class VarConfigPanel extends JPanel implements IConfigPanel {
	private static final long serialVersionUID = 5471235329179897180L;

	private JTextField baseDirText;
	private Map<String, JTextField> varTexts = new LinkedHashMap<>();

	public VarConfigPanel(ConfigProperties configProperties, final IConfigLog log) throws Exception {
		GridBagLayout layout = new GridBagLayout();
		GridBagConstraints gc = new GridBagConstraints();
		gc.fill = GridBagConstraints.BOTH;
		gc.gridwidth = 1;
		gc.weightx = 1.0;

		this.setLayout(layout);

		Properties cfgProps = configProperties.getProps();
		Map<String, String> varMap = getConfigMap(cfgProps);

		String varBasePkgKey = "basePackage";
		String varBasePkgValue = varMap.get(varBasePkgKey);

		Map<String, Object> map = new HashMap<>();
		map.putAll(varMap);
		map.put(varBasePkgKey, varBasePkgValue);

		JTextField varBasePkgTextField = createVarLine(varBasePkgKey, varBasePkgValue, layout, gc);
		varTexts.put(varBasePkgKey, varBasePkgTextField);
		varBasePkgTextField.addKeyListener(new KeyAdapter() {
			@Override
			public void keyReleased(KeyEvent e) {
				map.put(varBasePkgKey, varBasePkgTextField.getText());
				for (String key : varTexts.keySet()) {
					if (varBasePkgKey.equals(key)) {
						continue;
					}
					
					JTextField text = varTexts.get(key);
					text.setText(getVarPackageValue(varMap.get(key), map));
				}
			}
		});

		for (String varKey : varMap.keySet()) {
			if (varBasePkgKey.equals(varKey)) {
				continue;
			}
			String varValue = varMap.get(varKey);
			JTextField varText = createVarLine(varKey, getVarPackageValue(varValue, map), layout, gc);
			varTexts.put(varKey, varText);
		}

		JSeparator bottomSpt = new JSeparator(SwingConstants.HORIZONTAL);
		gc.gridwidth = GridBagConstraints.REMAINDER;
		layout.addLayoutComponent(bottomSpt, gc);
		this.add(bottomSpt);

		JPanel btnPanel = new JPanel();
		JButton curProjBtn = new JButton("当前项目路径");
		curProjBtn.addActionListener(e -> {
			setCurProjText();
		});
		btnPanel.add(curProjBtn);

		JButton desktopBtn = new JButton("桌面");
		desktopBtn.addActionListener(e -> {
			setDesktopText();
		});
		btnPanel.add(desktopBtn);

		JButton chooseBtn = new JButton("..选择");
		chooseBtn.addActionListener(e -> {
			JFileChooser chooser = new JFileChooser(System.getProperty("user.home") + "/Desktop");
	        chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
	        chooser.showOpenDialog(null);
	        File file = chooser.getSelectedFile();
	        if (file != null) {
		        baseDirText.setText(FileUtils.appendSeparatorSuffix(file.getPath()));
	        }
		});
		btnPanel.add(chooseBtn);

		gc.gridwidth = GridBagConstraints.REMAINDER;
		layout.addLayoutComponent(btnPanel, gc);
		this.add(btnPanel);

		JLabel baseDirLabel = new JLabel("存放路径： ", SwingConstants.RIGHT);
		baseDirText = new JTextField(cfgProps.getProperty("baseDir"), 45);
		gc.gridwidth = 1;
		layout.addLayoutComponent(baseDirLabel, gc);
		gc.gridwidth = GridBagConstraints.REMAINDER;
		layout.addLayoutComponent(baseDirText, gc);
		this.add(baseDirLabel);
		this.add(baseDirText);
	}

	private JTextField createVarLine(String varKey, String varValue, GridBagLayout layout, GridBagConstraints gc) {
		JLabel label = new JLabel(varKey + "：", SwingConstants.RIGHT);
		JTextField text = new JTextField(varValue, 45);

		gc.gridwidth = 1;
		layout.addLayoutComponent(label, gc);
		gc.gridwidth = GridBagConstraints.REMAINDER;
		layout.addLayoutComponent(text, gc);

		this.add(label);
		this.add(text);
		return text;
	}

	private String getVarPackageValue(String varValue, Map<String, Object> map) {
		return PlaceHolderHelper.replace(varValue, map);
	}

	private void setDesktopText() {
		baseDirText.setText(FileUtils.switchPathSeparator(System.getProperty("user.home") + "/Desktop/"));
	}

	private void setCurProjText() {
		baseDirText.setText("classpath:../../src/main/java/");
	}

	
	private Map<String, String> getConfigMap(Properties props) throws Exception {
		Map<String, String> map = new LinkedHashMap<>();
		
		Set<String> keySet = new TreeSet<>();
		keySet.addAll(props.stringPropertyNames());

		for (String key : keySet) {
			if (key.startsWith("var.")) {
				String varKey = key.substring(key.indexOf(".", 4) + 1);
				map.put(varKey, props.getProperty(key));
			}
		}
		return map;
	}

	@Override
	public Properties getConfig() {
		Properties cfgs = new Properties();
		int varIndex = 1;
        try {
            for (Entry<String, JTextField> entry : varTexts.entrySet()) {
                String text = entry.getValue().getText().trim();
                cfgs.setProperty("var." + fillVarIndex(varIndex++) + "." + entry.getKey(), text);
            }
        } catch (Exception e) {
            throw ExceptionUtils.wrap2Runtime(e);
        }
		
		cfgs.put("baseDir", baseDirText.getText());
		return cfgs;
	}
	
	private String fillVarIndex(int varIndex) {
        return varIndex < 10 ? "0" + varIndex : "" + varIndex;
    }

	@Override
	public void onWindowOpened() {}

	@Override
	public void onWindowClosed() {}
}